local skynet = require "skynet"
require  "tablelogic"



local CMD={}
local GAMECMD = require "game_proto"

local TableFrameSink = {tabAddr={}}
local Manager=nil
local Chairs = {}

local nPlayerCount = 0

local gJu = 1

function send_data(addr,msg)
    skynet.send(addr,"lua","send_data",msg)
end

function TableFrameSink:InitChair(num)
    TableLogic:InitChair(num)
end

function TableFrameSink:RegisterFun()    
    self.DoMsgList = {}
    self.DoMsgList[GAMECMD.Sub_ClientToGameSvr_TableModle_StandUpReq]       = {UnPackFormat = '',  Func = TableLogic.StandUp}
    self.DoMsgList[GAMECMD.Sub_ClientToGameSvr_TableModle_OutCardReq]       = {UnPackFormat = 'B', Func = TableLogic.OnOutCard}
    self.DoMsgList[GAMECMD.Sub_ClientToGameSvr_TableModle_DoAnGangReq]      = {UnPackFormat = 'B', Func = TableLogic.DoActionReq,     Type = WIKTYPE.WIK_ANGANG}
    self.DoMsgList[GAMECMD.Sub_ClientToGameSvr_TableModle_CanelAnGangReq]   = {UnPackFormat = '',  Func = TableLogic.CancelActionReq, Type = WIKTYPE.WIK_ANGANG}
    self.DoMsgList[GAMECMD.Sub_ClientToGameSvr_TableModle_DoJiaGangReq]     = {UnPackFormat = 'B', Func = TableLogic.DoActionReq,     Type = WIKTYPE.WIK_JIAGANG}
    self.DoMsgList[GAMECMD.Sub_ClientToGameSvr_TableModle_CanelJiaGangReq]  = {UnPackFormat = '',  Func = TableLogic.CancelActionReq, Type = WIKTYPE.WIK_JIAGANG}
    self.DoMsgList[GAMECMD.Sub_ClientToGameSvr_TableModle_CanelJieGangReq]  = {UnPackFormat = '',  Func = TableLogic.CancelActionReq, Type = WIKTYPE.WIK_JIEGANG}
    self.DoMsgList[GAMECMD.Sub_ClientToGameSvr_TableModle_CanelPengReq]     = {UnPackFormat = '',  Func = TableLogic.CancelActionReq, Type = WIKTYPE.WIK_PENG}
    self.DoMsgList[GAMECMD.Sub_ClientToGameSvr_TableModle_DoJieGangReq]     = {UnPackFormat = 'B', Func = TableLogic.DoActionReq,     Type = WIKTYPE.WIK_JIEGANG}
    self.DoMsgList[GAMECMD.Sub_ClientToGameSvr_TableModle_DoPengReq]        = {UnPackFormat = 'B', Func = TableLogic.DoActionReq,     Type = WIKTYPE.WIK_PENG}
    
    --self.DoMsgList[GAMECMD.Sub_ClientToGameSvr_TableModle_GoOnGameReq]      = {UnPackFormat = '',  Func = TableFrameSink.OnUserGoOnGameReq, Reciever = TableFrameSink}   --继续游戏
    
    self.DoMsgList[GAMECMD.Sub_ClientToGameSvr_TableModle_DoHuReq]          = {UnPackFormat = 'B', Func = TableLogic.DoActionReq,     Type = WIKTYPE.WIK_HU}
    self.DoMsgList[GAMECMD.Sub_ClientToGameSvr_TableModle_CancelHuReq]      = {UnPackFormat = '',  Func = TableLogic.CancelActionReq, Type = WIKTYPE.WIK_HU}
    
    self.DoMsgList[GAMECMD.Sub_ClientToGameSvr_TableModle_DoChiReq]         = {UnPackFormat = 'BBB', Func = TableLogic.DoActionReq,   Type = WIKTYPE.WIK_LINE}
    self.DoMsgList[GAMECMD.Sub_ClientToGameSvr_TableModle_CanelChiReq]      = {UnPackFormat = '',  Func = TableLogic.CancelActionReq, Type = WIKTYPE.WIK_LINE}
    
    TableLogic:RegisterFun()
end


function TableFrameSink.GetPlayerTableChair(Player)
    local play_id,chair_id,tabel_id=skynet.call(Manager,"lua","GetPlayerTableChair",Player)
    return play_id,chair_id,tabel_id
end

function TableFrameSink:OnStandUpReq(smsg, Player)
    local chair = TableLogic:PlayerToChair(Player)
    TableLogic:StandUp(chair)
    
    --[[reload_module("tablelogic")
    TableLogic:InitChair(nPlayerCount)
    for chair in TableLogic:ChairIterator() do     --重新填充地址
        chair.addr = TableFrameSink.tabAddr[chair.UserChairID]
        TableLogic.chairAddr[chair.addr] = chair
    end]]--
end

function TableFrameSink:OnUserGoOnGameReq()
    TableLogic:InitChair(nPlayerCount)
    TableFrameSink:BroadCastGameStart()
    
end

function TableFrameSink:BroadCastGameStart()
    TableLogic:InitChair(nPlayerCount)
    TableLogic:MakeReadyTable()
    TableLogic:BroadCastGameStart()
end

function TableFrameSink:StartFaPai(wJu)
    TableLogic:StartFaPai(wJu)
end


function TableFrameSink:DispatchCard()    --摸牌
    TableLogic:DispatchCard()
end

function TableFrameSink:BroadCastOutCard()
    TableLogic:BroadCastOutCard()
end

function TableFrameSink:DoMsg(act, smsg, Player)
    local chair = TableLogic:PlayerToChair(Player)
    if chair then 
        local reciever = TableLogic
        if act.Reciever then reciever = act.Reciever end
        if act.UnPackFormat == '' then 
            act.Func(reciever, chair, act.Type)
        else
            if act.Type then 
                 act.Func(reciever, chair, act.Type, string.unpack(act.UnPackFormat, smsg))
            else act.Func(reciever, chair, string.unpack(act.UnPackFormat, smsg))
            end
        end
        
    end
end

function TableFrameSink:OnGameMsg(scmd, smsg, Player)
    local data = string.sub(smsg, 5)
    local act = self.DoMsgList[scmd]
    if act then 
       self:DoMsg(act, data, Player) 
    end
end

function CMD.OnSitDownSucess(Player)
    local msg = string.pack(">I2>I2<I4<I4", 303, 2070, 2001, nPlayerCount)    --再告诉客户端几人麻将
    send_data(Player.nAgentAddr, msg)
        
    local i = 1
    repeat
        local chairAct = TableLogic:GetChair(i)
        if chairAct and not chairAct.addr then      --椅子还没有被占用,绑定地址
            --TableLogic.TableObj.m_pChairs[chairAct.UserChairID].Player = Player
            chairAct.addr = Player.nAgentAddr
            --TableFrameSink.tabAddr[chairAct.UserChairID] = Player.nAgentAddr
            TableLogic.chairAddr[chairAct.addr] = chairAct
            --TableFrameSink:OnSitDownSucess(Player)
            return chairAct.UserChairID
        end
        i = i + 1
    until i > nPlayerCount
end

function CMD.SetTableData(Table, nMaxPlayerCount, nDiFen, nMa, nFangPaoOrZiMo, nDianPaoMaOrZiMoMa, nKeQiangGang, externData)
    TableFrameSink:InitChair(nMaxPlayerCount)
    TableFrameSink:RegisterFun()
    TableLogic.TableObj = Table
    nPlayerCount = nMaxPlayerCount 
    local strMakeRoomMsg = string.format('南宁麻将 【%d】人 底分【%d】', nMaxPlayerCount, nDiFen)
    TableLogic.DiFen = nDiFen
    local strHp = ' 平胡点炮 '
    local strZm = ' 胡牌抓 '
    if nFangPaoOrZiMo == 0 then
        strHp = ' 平胡自摸 ' TableLogic.PingHuZiMo = true end     --为1表示平胡可以点炮，为0就是必须自摸
    if nDianPaoMaOrZiMoMa == 0 then 
        strZm = ' 自摸抓 '
        TableLogic.OnlyZiMoMa = true end        --为1表示胡了就可以买马，为0就是自摸才能买马
    if nMa == 0 then strZm = ' 不抓马  ' end
    strMakeRoomMsg = strMakeRoomMsg..strHp
    strMakeRoomMsg = strMakeRoomMsg..strZm
    local strMaCount = ''
    if nMa > 0 then strMaCount = string.format('【%d】匹马 ', nMa) end
    TableLogic.MaiMaCount = nMa
    strMakeRoomMsg = strMakeRoomMsg..strMaCount
    local num = nMaxPlayerCount
    for chair_id = 0 , num - 1 do 
        Table.m_pChairs[chair_id].m_isValid = 1
    end
    if num == 2 then 
        Table.m_pChairs[1].m_isValid = 0
        Table.m_pChairs[2].m_isValid = 1
    end
    
    return strMakeRoomMsg ,Table
end


function CMD.OnPlayerOfflineBack(Player, ChairId)
    local chair = TableLogic:UserIdToChair(ChairId)
    chair.addr = Player.nAgentAddr                          --重新获得地址
    TableLogic.chairAddr[chair.addr] = chair
    TableLogic:SendMeOfflineBackData(Player, ChairId)
end


function CMD.OnEventGameStart(Table, itableframe)
    if Table.m_wCurJu == 1 then 
        TableLogic.TableObj = Table
        TableLogic.ItableSrv = itableframe
    end
    TableFrameSink:BroadCastGameStart()
end

function CMD.TrySitDown(Player)
    local i = 1
    repeat
        local chairAct = TableLogic:GetChair(i)
        if chairAct and not chairAct.addr then      --椅子还没有被占用,绑定地址
            chairAct.addr = Player.nAgentAddr
            TableFrameSink.tabAddr[chairAct.UserChairID] = Player.nAgentAddr
            TableLogic.chairAddr[chairAct.addr] = chairAct
            TableFrameSink:OnSitDownSucess(Player)
            return chairAct.UserChairID
        end
        i = i + 1
    until i > nPlayerCount
end

function CMD.ConcluedGameLastRound()
    TableLogic:ConcluedGameLastRound()
    return true
end

function CMD.OneJuOver()
    TableLogic:OneJuOver()
end

function CMD.OnGameMessage(scmd,smsg,Player)
     skynet.error("[tableframe]",scmd)
     TableFrameSink:OnGameMsg(scmd, smsg, Player)
end

function CMD.ConcludeGame(...)
    TableLogic:ConcludeGame(...)
end

function CMD.CloseTableFrame()
    skynet.exit()
end

skynet.start(function()
    skynet.error("tableframe server start...")
	skynet.dispatch("lua", function(_,_, command, ...)
		local f = CMD[command]
		skynet.ret(skynet.pack(f(...)))
	end)
    Manager=skynet.localname(".manager")
    math.randomseed(os.time())
end)